home *** CD-ROM | disk | FTP | other *** search
/ AmigActive 2 / AACD 2.iso / AACD / Magazine / GraphicsCards / StormMesa / src / tritemp.h < prev    next >
Text File  |  1999-02-04  |  37KB  |  973 lines

  1. /* $Id: tritemp.h,v 3.3 1998/06/24 02:51:53 brianp Exp $ */
  2.  
  3. /*
  4.  * Mesa 3-D graphics library
  5.  * Version:  3.0
  6.  * Copyright (C) 1995-1998  Brian Paul
  7.  *
  8.  * This library is free software; you can redistribute it and/or
  9.  * modify it under the terms of the GNU Library General Public
  10.  * License as published by the Free Software Foundation; either
  11.  * version 2 of the License, or (at your option) any later version.
  12.  *
  13.  * This library is distributed in the hope that it will be useful,
  14.  * but WITHOUT ANY WARRANTY; without even the implied warranty of
  15.  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the GNU
  16.  * Library General Public License for more details.
  17.  *
  18.  * You should have received a copy of the GNU Library General Public
  19.  * License along with this library; if not, write to the Free
  20.  * Software Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
  21.  */
  22.  
  23.  
  24. /*
  25.  * $Log: tritemp.h,v $
  26.  * Revision 3.3  1998/06/24 02:51:53  brianp
  27.  * major clean-up of texture coordinate interpolation
  28.  *
  29.  * Revision 3.2  1998/02/20 04:53:07  brianp
  30.  * implemented GL_SGIS_multitexture
  31.  *
  32.  * Revision 3.1  1998/02/02 03:09:34  brianp
  33.  * added GL_LIGHT_MODEL_COLOR_CONTROL (separate specular color interpolation)
  34.  *
  35.  * Revision 3.0  1998/01/31 21:05:43  brianp
  36.  * initial rev
  37.  *
  38.  */
  39.  
  40.  
  41. /*
  42.  * Triangle Rasterizer Template
  43.  *
  44.  * This file is #include'd to generate custom triangle rasterizers.
  45.  *
  46.  * The following macros may be defined to indicate what auxillary information
  47.  * must be interplated across the triangle:
  48.  *    INTERP_Z      - if defined, interpolate Z values
  49.  *    INTERP_RGB    - if defined, interpolate RGB values
  50.  *    INTERP_SPEC   - if defined, interpolate specular RGB values
  51.  *    INTERP_ALPHA  - if defined, interpolate Alpha values
  52.  *    INTERP_INDEX  - if defined, interpolate color index values
  53.  *    INTERP_INT_ST - if defined, interpolate integer ST texcoords
  54.  *                         (fast, simple 2-D texture mapping)
  55.  *    INTERP_STUV   - if defined, interpolate set 0 float STRQ texcoords
  56.  *                         NOTE:  OpenGL STRQ = Mesa STUV (R was taken for red)
  57.  *    INTERP_STUV1  - if defined, interpolate set 1 float STRQ texcoords
  58.  *
  59.  * When one can directly address pixels in the color buffer the following
  60.  * macros can be defined and used to compute pixel addresses during
  61.  * rasterization (see pRow):
  62.  *    PIXEL_TYPE          - the datatype of a pixel (GLubyte, GLushort, GLuint)
  63.  *    BYTES_PER_ROW       - number of bytes per row in the color buffer
  64.  *    PIXEL_ADDRESS(X,Y)  - returns the address of pixel at (X,Y) where
  65.  *                          Y==0 at bottom of screen and increases upward.
  66.  *
  67.  * Optionally, one may provide one-time setup code per triangle:
  68.  *    SETUP_CODE    - code which is to be executed once per triangle
  69.  * 
  70.  * The following macro MUST be defined:
  71.  *    INNER_LOOP(LEFT,RIGHT,Y) - code to write a span of pixels.
  72.  *        Something like:
  73.  *
  74.  *                    for (x=LEFT; x<RIGHT;x++) {
  75.  *                       put_pixel(x,Y);
  76.  *                       // increment fixed point interpolants
  77.  *                    }
  78.  *
  79.  * This code was designed for the origin to be in the lower-left corner.
  80.  *
  81.  * Inspired by triangle rasterizer code written by Allen Akin.  Thanks Allen!
  82.  */
  83.  
  84.  
  85. /*void triangle( GLcontext *ctx, GLuint v0, GLuint v1, GLuint v2, GLuint pv )*/
  86. {
  87.    typedef struct {
  88.         GLint v0, v1;   /* Y(v0) < Y(v1) */
  89.         GLfloat dx;     /* X(v1) - X(v0) */
  90.         GLfloat dy;     /* Y(v1) - Y(v0) */
  91.         GLfixed fdxdy;  /* dx/dy in fixed-point */
  92.         GLfixed fsx;    /* first sample point x coord */
  93.         GLfixed fsy;
  94.         GLfloat adjy;   /* adjust from v[0]->fy to fsy, scaled */
  95.         GLint lines;    /* number of lines to be sampled on this edge */
  96.         GLfixed fx0;    /* fixed pt X of lower endpoint */
  97.    } EdgeT;
  98.  
  99.    struct vertex_buffer *VB = ctx->VB;
  100.    EdgeT eMaj, eTop, eBot;
  101.    GLfloat oneOverArea;
  102.    int vMin, vMid, vMax;       /* vertex indexes:  Y(vMin)<=Y(vMid)<=Y(vMax) */
  103.  
  104.    /* find the order of the 3 vertices along the Y axis */
  105.    {
  106.       GLfloat y0 = VB->Win[v0][1];
  107.       GLfloat y1 = VB->Win[v1][1];
  108.       GLfloat y2 = VB->Win[v2][1];
  109.  
  110.       if (y0<=y1) {
  111.          if (y1<=y2) {
  112.             vMin = v0;   vMid = v1;   vMax = v2;   /* y0<=y1<=y2 */
  113.          }
  114.          else if (y2<=y0) {
  115.             vMin = v2;   vMid = v0;   vMax = v1;   /* y2<=y0<=y1 */
  116.          }
  117.          else {
  118.             vMin = v0;   vMid = v2;   vMax = v1;   /* y0<=y2<=y1 */
  119.          }
  120.       }
  121.       else {
  122.          if (y0<=y2) {
  123.             vMin = v1;   vMid = v0;   vMax = v2;   /* y1<=y0<=y2 */
  124.          }
  125.          else if (y2<=y1) {
  126.             vMin = v2;   vMid = v1;   vMax = v0;   /* y2<=y1<=y0 */
  127.          }
  128.          else {
  129.             vMin = v1;   vMid = v2;   vMax = v0;   /* y1<=y2<=y0 */
  130.          }
  131.       }
  132.    }
  133.  
  134.    /* vertex/edge relationship */
  135.    eMaj.v0 = vMin;   eMaj.v1 = vMax;   /*TODO: .v1's not needed */
  136.    eTop.v0 = vMid;   eTop.v1 = vMax;
  137.    eBot.v0 = vMin;   eBot.v1 = vMid;
  138.  
  139.    /* compute deltas for each edge:  vertex[v1] - vertex[v0] */
  140.    eMaj.dx = VB->Win[vMax][0] - VB->Win[vMin][0];
  141.    eMaj.dy = VB->Win[vMax][1] - VB->Win[vMin][1];
  142.    eTop.dx = VB->Win[vMax][0] - VB->Win[vMid][0];
  143.    eTop.dy = VB->Win[vMax][1] - VB->Win[vMid][1];
  144.    eBot.dx = VB->Win[vMid][0] - VB->Win[vMin][0];
  145.    eBot.dy = VB->Win[vMid][1] - VB->Win[vMin][1];
  146.  
  147.    /* compute oneOverArea */
  148.    {
  149.       GLfloat area = eMaj.dx * eBot.dy - eBot.dx * eMaj.dy;
  150.       if (area>-0.05f && area<0.05f) {
  151.          return;  /* very small; CULLED */
  152.       }
  153.       oneOverArea = 1.0F / area;
  154.    }
  155.  
  156.    /* Edge setup.  For a triangle strip these could be reused... */
  157.    {
  158.       /* fixed point Y coordinates */
  159.       GLfixed vMin_fx = FloatToFixed(VB->Win[vMin][0] + 0.5F);
  160.       GLfixed vMin_fy = FloatToFixed(VB->Win[vMin][1] - 0.5F);
  161.       GLfixed vMid_fx = FloatToFixed(VB->Win[vMid][0] + 0.5F);
  162.       GLfixed vMid_fy = FloatToFixed(VB->Win[vMid][1] - 0.5F);
  163.       GLfixed vMax_fy = FloatToFixed(VB->Win[vMax][1] - 0.5F);
  164.  
  165.       eMaj.fsy = FixedCeil(vMin_fy);
  166.       eMaj.lines = FixedToInt(vMax_fy + FIXED_ONE - FIXED_EPSILON - eMaj.fsy);
  167.       if (eMaj.lines > 0) {
  168.          GLfloat dxdy = eMaj.dx / eMaj.dy;
  169.          eMaj.fdxdy = SignedFloatToFixed(dxdy);
  170.          eMaj.adjy = (GLfloat) (eMaj.fsy - vMin_fy);  /* SCALED! */
  171.          eMaj.fx0 = vMin_fx;
  172.          eMaj.fsx = eMaj.fx0 + (GLfixed) (eMaj.adjy * dxdy);
  173.       }
  174.       else {
  175.          return;  /*CULLED*/
  176.       }
  177.  
  178.       eTop.fsy = FixedCeil(vMid_fy);
  179.       eTop.lines = FixedToInt(vMax_fy + FIXED_ONE - FIXED_EPSILON - eTop.fsy);
  180.       if (eTop.lines > 0) {
  181.          GLfloat dxdy = eTop.dx / eTop.dy;
  182.          eTop.fdxdy = SignedFloatToFixed(dxdy);
  183.          eTop.adjy = (GLfloat) (eTop.fsy - vMid_fy); /* SCALED! */
  184.          eTop.fx0 = vMid_fx;
  185.          eTop.fsx = eTop.fx0 + (GLfixed) (eTop.adjy * dxdy);
  186.       }
  187.  
  188.       eBot.fsy = FixedCeil(vMin_fy);
  189.       eBot.lines = FixedToInt(vMid_fy + FIXED_ONE - FIXED_EPSILON - eBot.fsy);
  190.       if (eBot.lines > 0) {
  191.          GLfloat dxdy = eBot.dx / eBot.dy;
  192.          eBot.fdxdy = SignedFloatToFixed(dxdy);
  193.          eBot.adjy = (GLfloat) (eBot.fsy - vMin_fy);  /* SCALED! */
  194.          eBot.fx0 = vMin_fx;
  195.          eBot.fsx = eBot.fx0 + (GLfixed) (eBot.adjy * dxdy);
  196.       }
  197.    }
  198.  
  199.    /*
  200.     * Conceptually, we view a triangle as two subtriangles
  201.     * separated by a perfectly horizontal line.  The edge that is
  202.     * intersected by this line is one with maximal absolute dy; we
  203.     * call it a ``major'' edge.  The other two edges are the
  204.     * ``top'' edge (for the upper subtriangle) and the ``bottom''
  205.     * edge (for the lower subtriangle).  If either of these two
  206.     * edges is horizontal or very close to horizontal, the
  207.     * corresponding subtriangle might cover zero sample points;
  208.     * we take care to handle such cases, for performance as well
  209.     * as correctness.
  210.     *
  211.     * By stepping rasterization parameters along the major edge,
  212.     * we can avoid recomputing them at the discontinuity where
  213.     * the top and bottom edges meet.  However, this forces us to
  214.     * be able to scan both left-to-right and right-to-left. 
  215.     * Also, we must determine whether the major edge is at the
  216.     * left or right side of the triangle.  We do this by
  217.     * computing the magnitude of the cross-product of the major
  218.     * and top edges.  Since this magnitude depends on the sine of
  219.     * the angle between the two edges, its sign tells us whether
  220.     * we turn to the left or to the right when travelling along
  221.     * the major edge to the top edge, and from this we infer
  222.     * whether the major edge is on the left or the right.
  223.     *
  224.     * Serendipitously, this cross-product magnitude is also a
  225.     * value we need to compute the iteration parameter
  226.     * derivatives for the triangle, and it can be used to perform
  227.     * backface culling because its sign tells us whether the
  228.     * triangle is clockwise or counterclockwise.  In this code we
  229.     * refer to it as ``area'' because it's also proportional to
  230.     * the pixel area of the triangle.
  231.     */
  232.  
  233.    {
  234.       GLint ltor;               /* true if scanning left-to-right */
  235. #if INTERP_Z
  236.       GLfloat dzdx, dzdy;      GLfixed fdzdx;
  237. #endif
  238. #if INTERP_RGB
  239.       GLfloat drdx, drdy;      GLfixed fdrdx;
  240.       GLfloat dgdx, dgdy;      GLfixed fdgdx;
  241.       GLfloat dbdx, dbdy;      GLfixed fdbdx;
  242. #endif
  243. #if INTERP_SPEC
  244.       GLfloat dsrdx, dsrdy;    GLfixed fdsrdx;
  245.       GLfloat dsgdx, dsgdy;    GLfixed fdsgdx;
  246.       GLfloat dsbdx, dsbdy;    GLfixed fdsbdx;
  247. #endif
  248. #if INTERP_ALPHA
  249.       GLfloat dadx, dady;      GLfixed fdadx;
  250. #endif
  251. #if INTERP_INDEX
  252.       GLfloat didx, didy;      GLfixed fdidx;
  253. #endif
  254. #if INTERP_INT_ST
  255.       GLfloat dsdx, dsdy;      GLfixed fdsdx;
  256.       GLfloat dtdx, dtdy;      GLfixed fdtdx;
  257. #endif
  258. #if INTERP_STUV
  259.       GLfloat dsdx, dsdy;
  260.       GLfloat dtdx, dtdy;
  261.       GLfloat dudx, dudy;
  262.       GLfloat dvdx, dvdy;
  263. #endif
  264. #if INTERP_STUV1
  265.       GLfloat ds1dx, ds1dy;
  266.       GLfloat dt1dx, dt1dy;
  267.       GLfloat du1dx, du1dy;
  268.       GLfloat dv1dx, dv1dy;
  269. #endif
  270.  
  271.       /*
  272.        * Execute user-supplied setup code
  273.        */
  274. #ifdef SETUP_CODE
  275.       SETUP_CODE
  276. #endif
  277.  
  278.       ltor = (oneOverArea < 0.0F);
  279.  
  280.       /* compute d?/dx and d?/dy derivatives */
  281. #if INTERP_Z
  282.       {
  283.          GLfloat eMaj_dz, eBot_dz;
  284.          eMaj_dz = VB->Win[vMax][2] - VB->Win[vMin][2];
  285.          eBot_dz = VB->Win[vMid][2] - VB->Win[vMin][2];
  286.          dzdx = oneOverArea * (eMaj_dz * eBot.dy - eMaj.dy * eBot_dz);
  287.          if (dzdx>DEPTH_SCALE || dzdx<-DEPTH_SCALE) {
  288.             /* probably a sliver triangle */
  289.             dzdx = 0.0;
  290.             dzdy = 0.0;
  291.          }
  292.          else {
  293.             dzdy = oneOverArea * (eMaj.dx * eBot_dz - eMaj_dz * eBot.dx);
  294.          }
  295. #if DEPTH_BITS==16
  296.          fdzdx = SignedFloatToFixed(dzdx);
  297. #else
  298.          fdzdx = (GLint) dzdx;
  299. #endif
  300.       }
  301. #endif
  302. #if INTERP_RGB
  303.       {
  304.          GLfloat eMaj_dr, eBot_dr;
  305.          eMaj_dr = (GLint) VB->Color[vMax][0] - (GLint) VB->Color[vMin][0];
  306.          eBot_dr = (GLint) VB->Color[vMid][0] - (GLint) VB->Color[vMin][0];
  307.          drdx = oneOverArea * (eMaj_dr * eBot.dy - eMaj.dy * eBot_dr);
  308.          fdrdx = SignedFloatToFixed(drdx);
  309.          drdy = oneOverArea * (eMaj.dx * eBot_dr - eMaj_dr * eBot.dx);
  310.       }
  311.       {
  312.          GLfloat eMaj_dg, eBot_dg;
  313.          eMaj_dg = (GLint) VB->Color[vMax][1] - (GLint) VB->Color[vMin][1];
  314.          eBot_dg = (GLint) VB->Color[vMid][1] - (GLint) VB->Color[vMin][1];
  315.          dgdx = oneOverArea * (eMaj_dg * eBot.dy - eMaj.dy * eBot_dg);
  316.          fdgdx = SignedFloatToFixed(dgdx);
  317.          dgdy = oneOverArea * (eMaj.dx * eBot_dg - eMaj_dg * eBot.dx);
  318.       }
  319.       {
  320.          GLfloat eMaj_db, eBot_db;
  321.          eMaj_db = (GLint) VB->Color[vMax][2] - (GLint) VB->Color[vMin][2];
  322.          eBot_db = (GLint) VB->Color[vMid][2] - (GLint) VB->Color[vMin][2];
  323.          dbdx = oneOverArea * (eMaj_db * eBot.dy - eMaj.dy * eBot_db);
  324.          fdbdx = SignedFloatToFixed(dbdx);
  325.          dbdy = oneOverArea * (eMaj.dx * eBot_db - eMaj_db * eBot.dx);
  326.       }
  327. #endif
  328. #if INTERP_SPEC
  329.       {
  330.          GLfloat eMaj_dsr, eBot_dsr;
  331.          eMaj_dsr = (GLint) VB->Specular[vMax][0] - (GLint) VB->Specular[vMin][0];
  332.          eBot_dsr = (GLint) VB->Specular[vMid][0] - (GLint) VB->Specular[vMin][0];
  333.          dsrdx = oneOverArea * (eMaj_dsr * eBot.dy - eMaj.dy * eBot_dsr);
  334.          fdsrdx = SignedFloatToFixed(dsrdx);
  335.          dsrdy = oneOverArea * (eMaj.dx * eBot_dsr - eMaj_dsr * eBot.dx);
  336.       }
  337.       {
  338.          GLfloat eMaj_dsg, eBot_dsg;
  339.          eMaj_dsg = (GLint) VB->Specular[vMax][1] - (GLint) VB->Specular[vMin][1];
  340.          eBot_dsg = (GLint) VB->Specular[vMid][1] - (GLint) VB->Specular[vMin][1];
  341.          dsgdx = oneOverArea * (eMaj_dsg * eBot.dy - eMaj.dy * eBot_dsg);
  342.          fdsgdx = SignedFloatToFixed(dsgdx);
  343.          dsgdy = oneOverArea * (eMaj.dx * eBot_dsg - eMaj_dsg * eBot.dx);
  344.       }
  345.       {
  346.          GLfloat eMaj_dsb, eBot_dsb;
  347.          eMaj_dsb = (GLint) VB->Specular[vMax][2] - (GLint) VB->Specular[vMin][2];
  348.          eBot_dsb = (GLint) VB->Specular[vMid][2] - (GLint) VB->Specular[vMin][2];
  349.          dsbdx = oneOverArea * (eMaj_dsb * eBot.dy - eMaj.dy * eBot_dsb);
  350.          fdsbdx = SignedFloatToFixed(dsbdx);
  351.          dsbdy = oneOverArea * (eMaj.dx * eBot_dsb - eMaj_dsb * eBot.dx);
  352.       }
  353. #endif
  354. #if INTERP_ALPHA
  355.       {
  356.          GLfloat eMaj_da, eBot_da;
  357.          eMaj_da = (GLint) VB->Color[vMax][3] - (GLint) VB->Color[vMin][3];
  358.          eBot_da = (GLint) VB->Color[vMid][3] - (GLint) VB->Color[vMin][3];
  359.          dadx = oneOverArea * (eMaj_da * eBot.dy - eMaj.dy * eBot_da);
  360.          fdadx = SignedFloatToFixed(dadx);
  361.          dady = oneOverArea * (eMaj.dx * eBot_da - eMaj_da * eBot.dx);
  362.       }
  363. #endif
  364. #if INTERP_INDEX
  365.       {
  366.          GLfloat eMaj_di, eBot_di;
  367.          eMaj_di = (GLint) VB->Index[vMax] - (GLint) VB->Index[vMin];
  368.          eBot_di = (GLint) VB->Index[vMid] - (GLint) VB->Index[vMin];
  369.          didx = oneOverArea * (eMaj_di * eBot.dy - eMaj.dy * eBot_di);
  370.          fdidx = SignedFloatToFixed(didx);
  371.          didy = oneOverArea * (eMaj.dx * eBot_di - eMaj_di * eBot.dx);
  372.       }
  373. #endif
  374. #if INTERP_INT_ST
  375.       {
  376.          GLfloat eMaj_ds, eBot_ds;
  377.          eMaj_ds = (VB->MultiTexCoord[0][vMax][0] - VB->MultiTexCoord[0][vMin][0]) * S_SCALE;
  378.          eBot_ds = (VB->MultiTexCoord[0][vMid][0] - VB->MultiTexCoord[0][vMin][0]) * S_SCALE;
  379.          dsdx = oneOverArea * (eMaj_ds * eBot.dy - eMaj.dy * eBot_ds);
  380.          fdsdx = SignedFloatToFixed(dsdx);
  381.          dsdy = oneOverArea * (eMaj.dx * eBot_ds - eMaj_ds * eBot.dx);
  382.       }
  383.       {
  384.          GLfloat eMaj_dt, eBot_dt;
  385.          eMaj_dt = (VB->MultiTexCoord[0][vMax][1] - VB->MultiTexCoord[0][vMin][1]) * T_SCALE;
  386.          eBot_dt = (VB->MultiTexCoord[0][vMid][1] - VB->MultiTexCoord[0][vMin][1]) * T_SCALE;
  387.          dtdx = oneOverArea * (eMaj_dt * eBot.dy - eMaj.dy * eBot_dt);
  388.          fdtdx = SignedFloatToFixed(dtdx);
  389.          dtdy = oneOverArea * (eMaj.dx * eBot_dt - eMaj_dt * eBot.dx);
  390.       }
  391. #endif
  392. #if INTERP_STUV
  393.       {
  394.          GLfloat wMax = 1.0F / VB->Clip[vMax][3];
  395.          GLfloat wMin = 1.0F / VB->Clip[vMin][3];
  396.          GLfloat wMid = 1.0F / VB->Clip[vMid][3];
  397.          GLfloat eMaj_ds, eBot_ds;
  398.          GLfloat eMaj_dt, eBot_dt;
  399.          GLfloat eMaj_du, eBot_du;
  400.          GLfloat eMaj_dv, eBot_dv;
  401.  
  402.          eMaj_ds = VB->MultiTexCoord[0][vMax][0]*wMax - VB->MultiTexCoord[0][vMin][0]*wMin;
  403.          eBot_ds = VB->MultiTexCoord[0][vMid][0]*wMid - VB->MultiTexCoord[0][vMin][0]*wMin;
  404.          dsdx = oneOverArea * (eMaj_ds * eBot.dy - eMaj.dy * eBot_ds);
  405.          dsdy = oneOverArea * (eMaj.dx * eBot_ds - eMaj_ds * eBot.dx);
  406.  
  407.          eMaj_dt = VB->MultiTexCoord[0][vMax][1]*wMax - VB->MultiTexCoord[0][vMin][1]*wMin;
  408.          eBot_dt = VB->MultiTexCoord[0][vMid][1]*wMid - VB->MultiTexCoord[0][vMin][1]*wMin;
  409.          dtdx = oneOverArea * (eMaj_dt * eBot.dy - eMaj.dy * eBot_dt);
  410.          dtdy = oneOverArea * (eMaj.dx * eBot_dt - eMaj_dt * eBot.dx);
  411.          eMaj_du = VB->MultiTexCoord[0][vMax][2]*wMax - VB->MultiTexCoord[0][vMin][2]*wMin;
  412.          eBot_du = VB->MultiTexCoord[0][vMid][2]*wMid - VB->MultiTexCoord[0][vMin][2]*wMin;
  413.          dudx = oneOverArea * (eMaj_du * eBot.dy - eMaj.dy * eBot_du);
  414.          dudy = oneOverArea * (eMaj.dx * eBot_du - eMaj_du * eBot.dx);
  415.  
  416.          eMaj_dv = VB->MultiTexCoord[0][vMax][3]*wMax - VB->MultiTexCoord[0][vMin][3]*wMin;
  417.          eBot_dv = VB->MultiTexCoord[0][vMid][3]*wMid - VB->MultiTexCoord[0][vMin][3]*wMin;
  418.          dvdx = oneOverArea * (eMaj_dv * eBot.dy - eMaj.dy * eBot_dv);
  419.          dvdy = oneOverArea * (eMaj.dx * eBot_dv - eMaj_dv * eBot.dx);
  420.       }
  421. #endif
  422. #if INTERP_STUV1
  423.       {
  424.          GLfloat wMax = 1.0F / VB->Clip[vMax][3];
  425.          GLfloat wMin = 1.0F / VB->Clip[vMin][3];
  426.          GLfloat wMid = 1.0F / VB->Clip[vMid][3];
  427.          GLfloat eMaj_ds, eBot_ds;
  428.          GLfloat eMaj_dt, eBot_dt;
  429.          GLfloat eMaj_du, eBot_du;
  430.          GLfloat eMaj_dv, eBot_dv;
  431.          eMaj_ds = VB->MultiTexCoord[1][vMax][0]*wMax - VB->MultiTexCoord[1][vMin][0]*wMin;
  432.          eBot_ds = VB->MultiTexCoord[1][vMid][0]*wMid - VB->MultiTexCoord[1][vMin][0]*wMin;
  433.          ds1dx = oneOverArea * (eMaj_ds * eBot.dy - eMaj.dy * eBot_ds);
  434.          ds1dy = oneOverArea * (eMaj.dx * eBot_ds - eMaj_ds * eBot.dx);
  435.  
  436.          eMaj_dt = VB->MultiTexCoord[1][vMax][1]*wMax - VB->MultiTexCoord[1][vMin][1]*wMin;
  437.          eBot_dt = VB->MultiTexCoord[1][vMid][1]*wMid - VB->MultiTexCoord[1][vMin][1]*wMin;
  438.          dt1dx = oneOverArea * (eMaj_dt * eBot.dy - eMaj.dy * eBot_dt);
  439.          dt1dy = oneOverArea * (eMaj.dx * eBot_dt - eMaj_dt * eBot.dx);
  440.          eMaj_du = VB->MultiTexCoord[1][vMax][2]*wMax - VB->MultiTexCoord[1][vMin][2]*wMin;
  441.          eBot_du = VB->MultiTexCoord[1][vMid][2]*wMid - VB->MultiTexCoord[1][vMin][2]*wMin;
  442.          du1dx = oneOverArea * (eMaj_du * eBot.dy - eMaj.dy * eBot_du);
  443.          du1dy = oneOverArea * (eMaj.dx * eBot_du - eMaj_du * eBot.dx);
  444.  
  445.          eMaj_dv = VB->MultiTexCoord[1][vMax][3]*wMax - VB->MultiTexCoord[1][vMin][3]*wMin;
  446.          eBot_dv = VB->MultiTexCoord[1][vMid][3]*wMid - VB->MultiTexCoord[1][vMin][3]*wMin;
  447.          dv1dx = oneOverArea * (eMaj_dv * eBot.dy - eMaj.dy * eBot_dv);
  448.          dv1dy = oneOverArea * (eMaj.dx * eBot_dv - eMaj_dv * eBot.dx);
  449.       }
  450. #endif
  451.  
  452.       /*
  453.        * We always sample at pixel centers.  However, we avoid
  454.        * explicit half-pixel offsets in this code by incorporating
  455.        * the proper offset in each of x and y during the
  456.        * transformation to window coordinates.
  457.        *
  458.        * We also apply the usual rasterization rules to prevent
  459.        * cracks and overlaps.  A pixel is considered inside a
  460.        * subtriangle if it meets all of four conditions: it is on or
  461.        * to the right of the left edge, strictly to the left of the
  462.        * right edge, on or below the top edge, and strictly above
  463.        * the bottom edge.  (Some edges may be degenerate.)
  464.        *
  465.        * The following discussion assumes left-to-right scanning
  466.        * (that is, the major edge is on the left); the right-to-left
  467.        * case is a straightforward variation.
  468.        *
  469.        * We start by finding the half-integral y coordinate that is
  470.        * at or below the top of the triangle.  This gives us the
  471.        * first scan line that could possibly contain pixels that are
  472.        * inside the triangle.
  473.        *
  474.        * Next we creep down the major edge until we reach that y,
  475.        * and compute the corresponding x coordinate on the edge. 
  476.        * Then we find the half-integral x that lies on or just
  477.        * inside the edge.  This is the first pixel that might lie in
  478.        * the interior of the triangle.  (We won't know for sure
  479.        * until we check the other edges.)
  480.        *
  481.        * As we rasterize the triangle, we'll step down the major
  482.        * edge.  For each step in y, we'll move an integer number
  483.        * of steps in x.  There are two possible x step sizes, which
  484.        * we'll call the ``inner'' step (guaranteed to land on the
  485.        * edge or inside it) and the ``outer'' step (guaranteed to
  486.        * land on the edge or outside it).  The inner and outer steps
  487.        * differ by one.  During rasterization we maintain an error
  488.        * term that indicates our distance from the true edge, and
  489.        * select either the inner step or the outer step, whichever
  490.        * gets us to the first pixel that falls inside the triangle.
  491.        *
  492.        * All parameters (z, red, etc.) as well as the buffer
  493.        * addresses for color and z have inner and outer step values,
  494.        * so that we can increment them appropriately.  This method
  495.        * eliminates the need to adjust parameters by creeping a
  496.        * sub-pixel amount into the triangle at each scanline.
  497.        */
  498.  
  499.       {
  500.          int subTriangle;
  501.          GLfixed fx, fxLeftEdge, fxRightEdge, fdxLeftEdge, fdxRightEdge;
  502.          GLfixed fdxOuter;
  503.          int idxOuter;
  504.          float dxOuter;
  505.          GLfixed fError, fdError;
  506.          float adjx, adjy;
  507.          GLfixed fy;
  508.          int iy;
  509. #ifdef PIXEL_ADDRESS
  510.          PIXEL_TYPE *pRow;
  511.          int dPRowOuter, dPRowInner;  /* offset in bytes */
  512. #endif
  513. #if INTERP_Z
  514.          GLdepth *zRow;
  515.          int dZRowOuter, dZRowInner;  /* offset in bytes */
  516.          GLfixed fz, fdzOuter, fdzInner;
  517. #endif
  518. #if INTERP_RGB
  519.          GLfixed fr, fdrOuter, fdrInner;
  520.          GLfixed fg, fdgOuter, fdgInner;
  521.          GLfixed fb, fdbOuter, fdbInner;
  522. #endif
  523. #if INTERP_SPEC
  524.          GLfixed fsr, fdsrOuter, fdsrInner;
  525.          GLfixed fsg, fdsgOuter, fdsgInner;
  526.          GLfixed fsb, fdsbOuter, fdsbInner;
  527. #endif
  528. #if INTERP_ALPHA
  529.          GLfixed fa, fdaOuter, fdaInner;
  530. #endif
  531. #if INTERP_INDEX
  532.          GLfixed fi, fdiOuter, fdiInner;
  533. #endif
  534. #if INTERP_INT_ST
  535.          GLfixed fs, fdsOuter, fdsInner;
  536.          GLfixed ft, fdtOuter, fdtInner;
  537. #endif
  538. #if INTERP_STUV
  539.          GLfloat sLeft, dsOuter, dsInner;
  540.          GLfloat tLeft, dtOuter, dtInner;
  541.          GLfloat uLeft, duOuter, duInner;
  542.          GLfloat vLeft, dvOuter, dvInner;
  543. #endif
  544. #if INTERP_STUV1
  545.          GLfloat s1Left, ds1Outer, ds1Inner;
  546.          GLfloat t1Left, dt1Outer, dt1Inner;
  547.          GLfloat u1Left, du1Outer, du1Inner;
  548.          GLfloat v1Left, dv1Outer, dv1Inner;
  549. #endif
  550.  
  551.          for (subTriangle=0; subTriangle<=1; subTriangle++) {
  552.             EdgeT *eLeft, *eRight;
  553.             int setupLeft, setupRight;
  554.             int lines;
  555.  
  556.             if (subTriangle==0) {
  557.                /* bottom half */
  558.                if (ltor) {
  559.                   eLeft = &eMaj;
  560.                   eRight = &eBot;
  561.                   lines = eRight->lines;
  562.                   setupLeft = 1;
  563.                   setupRight = 1;
  564.                }
  565.                else {
  566.                   eLeft = &eBot;
  567.                   eRight = &eMaj;
  568.                   lines = eLeft->lines;
  569.                   setupLeft = 1;
  570.                   setupRight = 1;
  571.                }
  572.             }
  573.             else {
  574.                /* top half */
  575.                if (ltor) {
  576.                   eLeft = &eMaj;
  577.                   eRight = &eTop;
  578.                   lines = eRight->lines;
  579.                   setupLeft = 0;
  580.                   setupRight = 1;
  581.                }
  582.                else {
  583.                   eLeft = &eTop;
  584.                   eRight = &eMaj;
  585.                   lines = eLeft->lines;
  586.                   setupLeft = 1;
  587.                   setupRight = 0;
  588.                }
  589.                if (lines==0) return;
  590.             }
  591.  
  592.             if (setupLeft && eLeft->lines>0) {
  593.                GLint vLower;
  594.                GLfixed fsx = eLeft->fsx;
  595.                fx = FixedCeil(fsx);
  596.                fError = fx - fsx - FIXED_ONE;
  597.                fxLeftEdge = fsx - FIXED_EPSILON;
  598.                fdxLeftEdge = eLeft->fdxdy;
  599.                fdxOuter = FixedFloor(fdxLeftEdge - FIXED_EPSILON);
  600.                fdError = fdxOuter - fdxLeftEdge + FIXED_ONE;
  601.                idxOuter = FixedToInt(fdxOuter);
  602.                dxOuter = (float) idxOuter;
  603.  
  604.                fy = eLeft->fsy;
  605.                iy = FixedToInt(fy);
  606.  
  607.                adjx = (float)(fx - eLeft->fx0);  /* SCALED! */
  608.                adjy = eLeft->adjy;               /* SCALED! */
  609.  
  610.                vLower = eLeft->v0;
  611.  
  612. #ifdef PIXEL_ADDRESS
  613.                {
  614.                   pRow = PIXEL_ADDRESS( FixedToInt(fxLeftEdge), iy );
  615.                   dPRowOuter = -((int)BYTES_PER_ROW) + idxOuter * sizeof(PIXEL_TYPE);
  616.                   /* negative because Y=0 at bottom and increases upward */
  617.                }
  618. #endif
  619.                /*
  620.                 * Now we need the set of parameter (z, color, etc.) values at
  621.                 * the point (fx, fy).  This gives us properly-sampled parameter
  622.                 * values that we can step from pixel to pixel.  Furthermore,
  623.                 * although we might have intermediate results that overflow
  624.                 * the normal parameter range when we step temporarily outside
  625.                 * the triangle, we shouldn't overflow or underflow for any
  626.                 * pixel that's actually inside the triangle.
  627.                 */
  628.  
  629. #if INTERP_Z
  630.                {
  631.                   GLfloat z0, tmp;
  632.                   z0 = VB->Win[vLower][2] + ctx->PolygonZoffset;
  633. #if DEPTH_BITS==16
  634.                   /* interpolate fixed-pt values */
  635.                   tmp = (z0 * FIXED_SCALE + dzdx * adjx + dzdy * adjy) + FIXED_HALF;
  636.                   if (tmp < MAX_GLUINT/2)
  637.                      fz = (GLfixed) tmp;
  638.                   else
  639.                      fz = MAX_GLUINT/2;
  640.                   fdzOuter = SignedFloatToFixed(dzdy + dxOuter * dzdx);
  641. #else
  642.                   /* interpolate depth values exactly */
  643.                   fz = (GLint) (z0 + dzdx*FixedToFloat(adjx) + dzdy*FixedToFloat(adjy));
  644.                   fdzOuter = (GLint) (dzdy + dxOuter * dzdx);
  645. #endif
  646.                   zRow = Z_ADDRESS( ctx, FixedToInt(fxLeftEdge), iy );
  647.                   dZRowOuter = (ctx->Buffer->Width + idxOuter) * sizeof(GLdepth);
  648.                }
  649. #endif
  650. #if INTERP_RGB
  651.                fr = (GLfixed)(IntToFixed(VB->Color[vLower][0]) + drdx * adjx + drdy * adjy)
  652.                     + FIXED_HALF;
  653.                fdrOuter = SignedFloatToFixed(drdy + dxOuter * drdx);
  654.  
  655.                fg = (GLfixed)(IntToFixed(VB->Color[vLower][1]) + dgdx * adjx + dgdy * adjy)
  656.                     + FIXED_HALF;
  657.                fdgOuter = SignedFloatToFixed(dgdy + dxOuter * dgdx);
  658.  
  659.                fb = (GLfixed)(IntToFixed(VB->Color[vLower][2]) + dbdx * adjx + dbdy * adjy)
  660.                     + FIXED_HALF;
  661.                fdbOuter = SignedFloatToFixed(dbdy + dxOuter * dbdx);
  662. #endif
  663. #if INTERP_SPEC
  664.                fsr = (GLfixed)(IntToFixed(VB->Specular[vLower][0]) + dsrdx * adjx + dsrdy * adjy)
  665.                     + FIXED_HALF;
  666.                fdsrOuter = SignedFloatToFixed(dsrdy + dxOuter * dsrdx);
  667.  
  668.                fsg = (GLfixed)(IntToFixed(VB->Specular[vLower][1]) + dsgdx * adjx + dsgdy * adjy)
  669.                     + FIXED_HALF;
  670.                fdsgOuter = SignedFloatToFixed(dsgdy + dxOuter * dsgdx);
  671.  
  672.                fsb = (GLfixed)(IntToFixed(VB->Specular[vLower][2]) + dsbdx * adjx + dsbdy * adjy)
  673.                     + FIXED_HALF;
  674.                fdsbOuter = SignedFloatToFixed(dsbdy + dxOuter * dsbdx);
  675. #endif
  676. #if INTERP_ALPHA
  677.                fa = (GLfixed)(IntToFixed(VB->Color[vLower][3]) + dadx * adjx + dady * adjy)
  678.                     + FIXED_HALF;
  679.                fdaOuter = SignedFloatToFixed(dady + dxOuter * dadx);
  680. #endif
  681. #if INTERP_INDEX
  682.                fi = (GLfixed)(VB->Index[vLower] * FIXED_SCALE + didx * adjx
  683.                               + didy * adjy) + FIXED_HALF;
  684.                fdiOuter = SignedFloatToFixed(didy + dxOuter * didx);
  685. #endif
  686. #if INTERP_INT_ST
  687.                {
  688.                   GLfloat s0, t0;
  689.                   s0 = VB->MultiTexCoord[0][vLower][0] * S_SCALE;
  690.                   fs = (GLfixed)(s0 * FIXED_SCALE + dsdx * adjx + dsdy * adjy) + FIXED_HALF;
  691.                   fdsOuter = SignedFloatToFixed(dsdy + dxOuter * dsdx);
  692.                   t0 = VB->MultiTexCoord[0][vLower][1] * T_SCALE;
  693.                   ft = (GLfixed)(t0 * FIXED_SCALE + dtdx * adjx + dtdy * adjy) + FIXED_HALF;
  694.                   fdtOuter = SignedFloatToFixed(dtdy + dxOuter * dtdx);
  695.                }
  696. #endif
  697. #if INTERP_STUV
  698.                {
  699.                   GLfloat invW = 1.0F / VB->Clip[vLower][3];
  700.                   GLfloat s0, t0, u0, v0;
  701.                   s0 = VB->MultiTexCoord[0][vLower][0] * invW;
  702.                   sLeft = s0 + (dsdx * adjx + dsdy * adjy) * (1.0F/FIXED_SCALE);
  703.                   dsOuter = dsdy + dxOuter * dsdx;
  704.                   t0 = VB->MultiTexCoord[0][vLower][1] * invW;
  705.                   tLeft = t0 + (dtdx * adjx + dtdy * adjy) * (1.0F/FIXED_SCALE);
  706.                   dtOuter = dtdy + dxOuter * dtdx;
  707.                   u0 = VB->MultiTexCoord[0][vLower][2] * invW;
  708.                   uLeft = u0 + (dudx * adjx + dudy * adjy) * (1.0F/FIXED_SCALE);
  709.                   duOuter = dudy + dxOuter * dudx;
  710.                   v0 = VB->MultiTexCoord[0][vLower][3] * invW;
  711.                   vLeft = v0 + (dvdx * adjx + dvdy * adjy) * (1.0F/FIXED_SCALE);
  712.                   dvOuter = dvdy + dxOuter * dvdx;
  713.                }
  714. #endif
  715. #if INTERP_STUV1
  716.                {
  717.                   GLfloat invW = 1.0F / VB->Clip[vLower][3];
  718.                   GLfloat s0, t0, u0, v0;
  719.                   s0 = VB->MultiTexCoord[1][vLower][0] * invW;
  720.                   s1Left = s0 + (ds1dx * adjx + ds1dy * adjy) * (1.0F/FIXED_SCALE);
  721.                   ds1Outer = ds1dy + dxOuter * ds1dx;
  722.                   t0 = VB->MultiTexCoord[1][vLower][1] * invW;
  723.                   t1Left = t0 + (dt1dx * adjx + dt1dy * adjy) * (1.0F/FIXED_SCALE);
  724.                   dt1Outer = dt1dy + dxOuter * dt1dx;
  725.                   u0 = VB->MultiTexCoord[1][vLower][2] * invW;
  726.                   u1Left = u0 + (du1dx * adjx + du1dy * adjy) * (1.0F/FIXED_SCALE);
  727.                   du1Outer = du1dy + dxOuter * du1dx;
  728.                   v0 = VB->MultiTexCoord[1][vLower][3] * invW;
  729.                   v1Left = v0 + (dv1dx * adjx + dv1dy * adjy) * (1.0F/FIXED_SCALE);
  730.                   dv1Outer = dv1dy + dxOuter * dv1dx;
  731.                }
  732. #endif
  733.  
  734.             } /*if setupLeft*/
  735.  
  736.  
  737.             if (setupRight && eRight->lines>0) {
  738.                fxRightEdge = eRight->fsx - FIXED_EPSILON;
  739.                fdxRightEdge = eRight->fdxdy;
  740.             }
  741.  
  742.             if (lines==0) {
  743.                continue;
  744.             }
  745.  
  746.  
  747.             /* Rasterize setup */
  748. #ifdef PIXEL_ADDRESS
  749.             dPRowInner = dPRowOuter + sizeof(PIXEL_TYPE);
  750. #endif
  751. #if INTERP_Z
  752.             dZRowInner = dZRowOuter + sizeof(GLdepth);
  753.             fdzInner = fdzOuter + fdzdx;
  754. #endif
  755. #if INTERP_RGB
  756.             fdrInner = fdrOuter + fdrdx;
  757.             fdgInner = fdgOuter + fdgdx;
  758.             fdbInner = fdbOuter + fdbdx;
  759. #endif
  760. #if INTERP_SPEC
  761.             fdsrInner = fdsrOuter + fdsrdx;
  762.             fdsgInner = fdsgOuter + fdsgdx;
  763.             fdsbInner = fdsbOuter + fdsbdx;
  764. #endif
  765. #if INTERP_ALPHA
  766.             fdaInner = fdaOuter + fdadx;
  767. #endif
  768. #if INTERP_INDEX
  769.             fdiInner = fdiOuter + fdidx;
  770. #endif
  771. #if INTERP_INT_ST
  772.             fdsInner = fdsOuter + fdsdx;
  773.             fdtInner = fdtOuter + fdtdx;
  774. #endif
  775. #if INTERP_STUV
  776.             dsInner = dsOuter + dsdx;
  777.             dtInner = dtOuter + dtdx;
  778.             duInner = duOuter + dudx;
  779.             dvInner = dvOuter + dvdx;
  780. #endif
  781. #if INTERP_STUV1
  782.             ds1Inner = ds1Outer + ds1dx;
  783.             dt1Inner = dt1Outer + dt1dx;
  784.             du1Inner = du1Outer + du1dx;
  785.             dv1Inner = dv1Outer + dv1dx;
  786. #endif
  787.  
  788.             while (lines>0) {
  789.                /* initialize the span interpolants to the leftmost value */
  790.                /* ff = fixed-pt fragment */
  791. #if INTERP_Z
  792.                GLfixed ffz = fz;
  793.                /*GLdepth *zp = zRow;*/
  794. #endif
  795. #if INTERP_RGB
  796.                GLfixed ffr = fr,  ffg = fg,  ffb = fb;
  797. #endif
  798. #if INTERP_SPEC
  799.                GLfixed ffsr = fsr,  ffsg = fsg,  ffsb = fsb;
  800. #endif
  801. #if INTERP_ALPHA
  802.                GLfixed ffa = fa;
  803. #endif
  804. #if INTERP_INDEX
  805.                GLfixed ffi = fi;
  806. #endif
  807. #if INTERP_INT_ST
  808.                GLfixed ffs = fs,  fft = ft;
  809. #endif
  810. #if INTERP_STUV
  811.                GLfloat ss = sLeft, tt = tLeft, uu = uLeft, vv = vLeft;
  812. #endif
  813. #if INTERP_STUV1
  814.                GLfloat ss1 = s1Left, tt1 = t1Left, uu1 = u1Left, vv1 = v1Left;
  815. #endif
  816.                GLint left = FixedToInt(fxLeftEdge);
  817.                GLint right = FixedToInt(fxRightEdge);
  818.  
  819. #if INTERP_RGB
  820.                {
  821.                   /* need this to accomodate round-off errors */
  822.                   GLfixed ffrend = ffr+(right-left-1)*fdrdx;
  823.                   GLfixed ffgend = ffg+(right-left-1)*fdgdx;
  824.                   GLfixed ffbend = ffb+(right-left-1)*fdbdx;
  825.                   if (ffrend<0) ffr -= ffrend;
  826.                   if (ffgend<0) ffg -= ffgend;
  827.                   if (ffbend<0) ffb -= ffbend;
  828.                   if (ffr<0) ffr = 0;
  829.                   if (ffg<0) ffg = 0;
  830.                   if (ffb<0) ffb = 0;
  831.                }
  832. #endif
  833. #if INTERP_SPEC
  834.                {
  835.                   /* need this to accomodate round-off errors */
  836.                   GLfixed ffsrend = ffsr+(right-left-1)*fdsrdx;
  837.                   GLfixed ffsgend = ffsg+(right-left-1)*fdsgdx;
  838.                   GLfixed ffsbend = ffsb+(right-left-1)*fdsbdx;
  839.                   if (ffsrend<0) ffsr -= ffsrend;
  840.                   if (ffsgend<0) ffsg -= ffsgend;
  841.                   if (ffsbend<0) ffsb -= ffsbend;
  842.                   if (ffsr<0) ffsr = 0;
  843.                   if (ffsg<0) ffsg = 0;
  844.                   if (ffsb<0) ffsb = 0;
  845.                }
  846. #endif
  847. #if INTERP_ALPHA
  848.                {
  849.                   GLfixed ffaend = ffa+(right-left-1)*fdadx;
  850.                   if (ffaend<0) ffa -= ffaend;
  851.                   if (ffa<0) ffa = 0;
  852.                }
  853. #endif
  854. #if INTERP_INDEX
  855.                if (ffi<0) ffi = 0;
  856. #endif
  857.  
  858.                INNER_LOOP( left, right, iy );
  859.  
  860.                /*
  861.                 * Advance to the next scan line.  Compute the
  862.                 * new edge coordinates, and adjust the
  863.                 * pixel-center x coordinate so that it stays
  864.                 * on or inside the major edge.
  865.                 */
  866.                iy++;
  867.                lines--;
  868.  
  869.                fxLeftEdge += fdxLeftEdge;
  870.                fxRightEdge += fdxRightEdge;
  871.  
  872.  
  873.                fError += fdError;
  874.                if (fError >= 0) {
  875.                   fError -= FIXED_ONE;
  876. #ifdef PIXEL_ADDRESS
  877.                   pRow = (PIXEL_TYPE*) ((GLubyte*)pRow + dPRowOuter);
  878. #endif
  879. #if INTERP_Z
  880.                   zRow = (GLdepth*) ((GLubyte*)zRow + dZRowOuter);
  881.                   fz += fdzOuter;
  882. #endif
  883. #if INTERP_RGB
  884.                   fr += fdrOuter;   fg += fdgOuter;   fb += fdbOuter;
  885. #endif
  886. #if INTERP_SPEC
  887.                   fsr += fdsrOuter;   fsg += fdsgOuter;   fsb += fdsbOuter;
  888. #endif
  889. #if INTERP_ALPHA
  890.                   fa += fdaOuter;
  891. #endif
  892. #if INTERP_INDEX
  893.                   fi += fdiOuter;
  894. #endif
  895. #if INTERP_INT_ST
  896.                   fs += fdsOuter;   ft += fdtOuter;
  897. #endif
  898. #if INTERP_STUV
  899.                   sLeft += dsOuter;
  900.                   tLeft += dtOuter;
  901.                   uLeft += duOuter;
  902.                   vLeft += dvOuter;
  903. #endif
  904. #if INTERP_STUV1
  905.                   s1Left += ds1Outer;
  906.                   t1Left += dt1Outer;
  907.                   u1Left += du1Outer;
  908.                   v1Left += dv1Outer;
  909. #endif
  910.                }
  911.                else {
  912. #ifdef PIXEL_ADDRESS
  913.                   pRow = (PIXEL_TYPE*) ((GLubyte*)pRow + dPRowInner);
  914. #endif
  915. #if INTERP_Z
  916.                   zRow = (GLdepth*) ((GLubyte*)zRow + dZRowInner);
  917.                   fz += fdzInner;
  918. #endif
  919. #if INTERP_RGB
  920.                   fr += fdrInner;   fg += fdgInner;   fb += fdbInner;
  921. #endif
  922. #if INTERP_SPEC
  923.                   fsr += fdsrInner;   fsg += fdsgInner;   fsb += fdsbInner;
  924. #endif
  925. #if INTERP_ALPHA
  926.                   fa += fdaInner;
  927. #endif
  928. #if INTERP_INDEX
  929.                   fi += fdiInner;
  930. #endif
  931. #if INTERP_INT_ST
  932.                   fs += fdsInner;   ft += fdtInner;
  933. #endif
  934. #if INTERP_STUV
  935.                   sLeft += dsInner;
  936.                   tLeft += dtInner;
  937.                   uLeft += duInner;
  938.                   vLeft += dvInner;
  939. #endif
  940. #if INTERP_STUV1
  941.                   s1Left += ds1Inner;
  942.                   t1Left += dt1Inner;
  943.                   u1Left += du1Inner;
  944.                   v1Left += dv1Inner;
  945. #endif
  946.                }
  947.             } /*while lines>0*/
  948.  
  949.          } /* for subTriangle */
  950.  
  951.       }
  952.    }
  953. }
  954.  
  955. #undef SETUP_CODE
  956. #undef INNER_LOOP
  957.  
  958. #undef PIXEL_TYPE
  959. #undef BYTES_PER_ROW
  960. #undef PIXEL_ADDRESS
  961.  
  962. #undef INTERP_Z
  963. #undef INTERP_RGB
  964. #undef INTERP_SPEC
  965. #undef INTERP_ALPHA
  966. #undef INTERP_INDEX
  967. #undef INTERP_INT_ST
  968. #undef INTERP_STUV
  969. #undef INTERP_STUV1
  970.  
  971. #undef S_SCALE
  972. #undef T_SCALE
  973.